package com.mes.schedule.manager;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.Date;
import java.util.List;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import com.mes.basicdata.manager.CalendarDataManager;
import com.mes.schedule.domain.SDevice;
import com.mes.schedule.domain.SOperationTask;
import com.mes.schedule.domain.SWorkCenter;
import com.mes.schedule.domain.ScheduleScheme;
import com.mes.schedule.domain.WorkCenterStatistics;
import com.mes.schedule.manager.iface.IScheduleWorkCenterManager;
import com.mes.schedule.util.ScheduleUtils;

@Component("scheduleWorkCenterManager")
@Transactional
public class ScheduleWorkCenterManager implements IScheduleWorkCenterManager{
	private final static Log log = LogFactory
			.getLog(ScheduleWorkCenterManager.class);
	 
	private ScheduleCalendarManager calendarManager;
	 
	private ScheduleDeviceManager scheduleDeviceManager;
	 
	private CalendarDataManager calendarDataManager;
	 
	private ScheduleOperationTaskManager scheduleOperationTaskManager;

	public CalendarDataManager getCalendarDataManager() {
		return calendarDataManager;
	}

	public void setCalendarManager(ScheduleCalendarManager calendarManager) {
		this.calendarManager = calendarManager;
	}



	public ScheduleOperationTaskManager getScheduleOperationTaskManager() {
		return scheduleOperationTaskManager;
	}

	public void setScheduleOperationTaskManager(
			ScheduleOperationTaskManager scheduleOperationTaskManager) {
		this.scheduleOperationTaskManager = scheduleOperationTaskManager;
	}

	public void setCalendarDataManager(CalendarDataManager calendarDataManager) {
		this.calendarDataManager = calendarDataManager;
	}

	 
	public double calCapacity(SWorkCenter workCenter, Date beforeDate) {
		double sumCapacity = 0d;
		for (SDevice device : workCenter.getSDeviceList()) {
			sumCapacity += this.scheduleDeviceManager.calCapacity(device,
					beforeDate);
		}
		return sumCapacity;
	}

	 
	public void calcWaitTime(SDevice device, ScheduleScheme scheme) {
		// TODO Auto-generated method stub

	}

	public ScheduleDeviceManager getScheduleDeviceManager() {
		return scheduleDeviceManager;
	}

	public void setScheduleDeviceManager(
			ScheduleDeviceManager scheduleDeviceManager) {
		this.scheduleDeviceManager = scheduleDeviceManager;
	}

//	 
//	public List<SOperationTask> getMustDoList(SWorkCenter sWorkCenter,
//			Date beforeDate, Double slackFactor, String drawingId,
//			Integer maxTaskInstance) {
//		ScheduleScheme scheme = sWorkCenter.getScheme();
//		List<SOperationTask> mustDoList = new ArrayList<SOperationTask>();
//		for (SOperationTask so : scheme.getScheduleOperationTasks()) {
//			if (so.getSWorkCenter() == sWorkCenter) {
//				if (maxTaskInstance != null
//						&& so.getTaskDistance() > maxTaskInstance)
//					continue;
//
//				if (so.getControlFinish() != null
//						&& so.getControlFinish().before(beforeDate))
//					mustDoList.add(so);
//				else if (so.getSlackFactor() != null && slackFactor != null
//						&& so.getSlackFactor() <= slackFactor)
//					mustDoList.add(so);
//			}
//
//		}
//		return mustDoList;
//	}

	 
	public List<WorkCenterStatistics> calWorkCenterLoad(String scheduleUid,
			Date beforeDate, Double slackFactorUbound,
			Integer criticalLevleLbound) throws Exception {
		// TODO Auto-generated method stub

		
		List<WorkCenterStatistics> wcsList=new ArrayList<WorkCenterStatistics>();
		ScheduleScheme scheme=ScheduleUtils.getScheduleScheme(scheduleUid);
		if(scheme==null)return null;	
		
		for(SWorkCenter workCenter:scheme.getWorkCenterMap().values())
		{
			if(workCenter.getIsVirtual())continue;
			WorkCenterStatistics wcs=new WorkCenterStatistics(workCenter);
			
			wcs.setCapacity(this.calCapacity(workCenter, beforeDate)/60);
			List<SOperationTask> mustDoList=this.scheduleOperationTaskManager.getMustDoList(workCenter, beforeDate, slackFactorUbound, null, null);
			double totalSetupTime=0;
			double totalRunTime=0;
			if(mustDoList!=null&&mustDoList.size()>0)
			{
				for(SOperationTask so:mustDoList)
				{
					double setupTime=so.getCompleteQty()>0?0:so.getEstiPreTime();
					double runTime=so.getEstiRunTime()*(so.getPlanQty()-so.getCompleteQty());
					totalSetupTime+=setupTime;
					totalRunTime+=runTime;
				}
				wcs.setSetupTime(totalSetupTime/60);
				wcs.setRunTime(totalRunTime/60);

			}
			
			if(wcs.getCapacity()>0)
			{
				wcs.setLoadRation(wcs.getLoad()/wcs.getCapacity()*100);
				wcs.setUtilRation(wcs.getRunTime()/wcs.getCapacity()*100);
			}
			
	
			
			wcsList.add(wcs);
		
		
		
		}
		
		Collections.sort(wcsList, new Comparator<WorkCenterStatistics>() {
			public int compare(WorkCenterStatistics o1, WorkCenterStatistics o2) {
				int i=1;
				if (o1.getLoadRation()>o2.getLoadRation()) {
					i=  -1;
				}
				return i;
			}
		});		
		
		return wcsList;
	}

	@Override
	public List<WorkCenterStatistics> calWorkCenterLoad(String scheduleUid, Date startTime, Date lateFinish,
			Double slackFactor, Double correctedFactor) throws Exception {
		// TODO Auto-generated method stub
		return null;
	}
}